import { v4 as uuidv4 } from 'uuid';

// 定义服务类型
export enum AgentServiceType {
  ADVISOR = 'finpilot_agent_service',
  DOC_ANALYSIS = 'doc_analysis_agent_service',
  ASSISTANT = 'credit_flow_assist_service_v2',
  B2B = 'credit_flow_assist_service'
}

export interface StreamMessage {
  id: string;
  text: string;
  role: 'user' | 'agent';
  status: 'sending' | 'sent' | 'error';
  timestamp: number;
  contentType?: 'text' | 'markdown';
  metadata?: {
    processingTime?: number;
    serviceId?: string;
    isStreamed?: boolean;
    firstTokenTime?: number; // 首Token时间延迟(秒)
    totalDelta?: number; // 总处理时间延迟(秒)
  };
}

export interface StreamBody {
  type: 'start' | 'task_start' | 'llm_output' | 'json_block' | 'llm_end' | 'task_complete';
  data: {
    content: string;
    result: string;
    phase?: 'reasoning' | 'llm'; // 添加phase字段支持
  }
  timestamp?: string;
}

// 思考过程回调接口
export interface ThinkingCallbacks {
  onThinkingStart?: () => void;
  onThinkingChunk?: (chunk: string, accumulated: string) => void;
  onThinkingComplete?: (fullThinking: string) => void;
  onLlmStart?: () => void;
}

// 扩展onChunk回调，添加phase信息
export type EnhancedChunkCallback = (chunk: string, accumulated: string, phase?: 'reasoning' | 'llm') => void;

class StreamApiService {
  private currentService: string = AgentServiceType.ADVISOR;
  private sessionId: string;
  private currentController: AbortController | null = null;

  constructor() {
    this.sessionId = uuidv4();
  }

  // 设置服务类型
  setServiceType(serviceType: string): void {
    this.currentService = serviceType;
  }

  // 获取当前服务类型
  getCurrentService(): string {
    return this.currentService;
  }

  // 发送消息到智能体（流式响应）
  async sendMessageStream(
    message: string,
    onChunk: EnhancedChunkCallback, // 使用增强的回调类型
    onComplete: (fullMessage: StreamMessage) => void,
    onError: (error: string) => void,
    userName?: string,
    sessionId?: string,
    docIds?: string[], // 文档ID列表 
    service_id?: string,
    background?: string,
    enableThinking?: boolean,
    thinkingCallbacks?: ThinkingCallbacks, // 添加思考过程回调
  ): Promise<void> {
    const startTime = Date.now();
    const messageId = Date.now().toString();
    let accumulatedText = '';
    let accumulatedThinking = ''; // 累积的思考过程
    let firstTokenTime: number | undefined = undefined; // 记录首Token时间
    let endTime: number | undefined = undefined; // 记录结束时间
    let isInThinkingPhase = false;
    let hasThinkingStarted = false;

    try {
      // 创建AbortController用于终止请求
      this.currentController = new AbortController();

      // 获取基础URL
      const baseURL = '/langchain-backend';

      console.log('enableThinking', enableThinking);
      // 构建请求参数
      const requestParams: any = {
        input: message,
        background: background || '',
        session_id: sessionId || this.sessionId,
        user_name: userName,
        agent_args: {
          "enable_thinking": enableThinking !== undefined ? enableThinking : true
        }
      };

      // 如果有docIds，添加到请求参数中
      if (docIds && docIds.length > 0) {
        requestParams.docIds = docIds;
      }

      const path = service_id === 'market_agent' ? 'market/generate_stream' : 'service_run_stream';
      const response = await fetch(`${baseURL}/${path}`, {
        method: 'POST',
        headers: {
          'Content-Type': 'application/json',
        },
        body: JSON.stringify({
          service_id: service_id || 'auto',
          params: requestParams
        }),
        signal: this.currentController.signal
      });

      if (!response.ok) {
        throw new Error(`HTTP ${response.status}: ${response.statusText}`);
      }

      if (!response.body) {
        throw new Error('响应体为空');
      }

      const reader = response.body.getReader();
      const decoder = new TextDecoder();

      while (true) {
        const { done, value } = await reader.read();

        if (done) {
          break;
        }

        const chunk = decoder.decode(value, { stream: true });
        const lines = chunk.split('\n');

        for (const line of lines) {
          if (line.trim() === '') continue;

          // 处理SSE格式数据
          if (line.startsWith('data:')) {
            const dataStr = line.slice(5).trim();

            if (dataStr === '[DONE]') {
              break;
            }

            try {
              const data = JSON.parse(dataStr) as StreamBody;
              const type = data.type;
              const phase = data.data.phase;

              // 检查是否为完成状态
              if (type === 'task_complete') {
                endTime = Date.now();
                // 思考阶段结束
                if (isInThinkingPhase && thinkingCallbacks?.onThinkingComplete) {
                  thinkingCallbacks.onThinkingComplete(accumulatedThinking);
                  isInThinkingPhase = false;
                }
              }

              // 根据实际API格式解析数据
              let chunkText = '';
              if ((path === 'service_run_stream' && ['llm_output'].includes(type) || path === 'market/generate_stream' && ['json_block'].includes(type)) 
                  && data.data.content !== "\n") {
                chunkText = data.data.content ? data.data.content : '';

                // 根据phase处理不同阶段
                if (phase === 'reasoning') {
                  // 思考阶段
                  if (!hasThinkingStarted && thinkingCallbacks?.onThinkingStart) {
                    thinkingCallbacks.onThinkingStart();
                    hasThinkingStarted = true;
                    isInThinkingPhase = true;
                  }

                  if (isInThinkingPhase) {
                    accumulatedThinking += chunkText;
                    thinkingCallbacks?.onThinkingChunk?.(chunkText, accumulatedThinking);
                    // 也通知主回调，但标明是reasoning阶段
                    onChunk(chunkText, accumulatedThinking, 'reasoning');
                  }
                } else if (phase === 'llm' || !phase) {
                  // LLM输出阶段
                  if (isInThinkingPhase) {
                    // 从思考阶段切换到LLM阶段
                    if (thinkingCallbacks?.onThinkingComplete) {
                      thinkingCallbacks.onThinkingComplete(accumulatedThinking);
                    }
                    if (thinkingCallbacks?.onLlmStart) {
                      thinkingCallbacks.onLlmStart();
                    }
                    isInThinkingPhase = false;
                  }

                  // 记录首Token时间（LLM输出的第一个token）
                  if (!firstTokenTime) {
                    firstTokenTime = Date.now();
                  }

                  accumulatedText += chunkText;
                  // 检查并移除accumulatedText中的```，防止多余markdown代码块符号
                  if (accumulatedText.includes('```')) {
                    accumulatedText = accumulatedText.replace(/```/g, '');
                  }
                  // 检查卡片占位符前后是否有\n或\n\n，按需补足
                  const cardPlaceholderRegex = /\[CARD:[^\]]+\]/g;
                  const matches = [...accumulatedText.matchAll(cardPlaceholderRegex)];
                  if (matches.length > 0) {
                    const lastMatch = matches[matches.length - 1];
                    let startIdx = lastMatch.index!;
                    let endIdx = startIdx + lastMatch[0].length;
                    // 检查前面
                    const before = accumulatedText.slice(Math.max(0, startIdx - 2), startIdx);
                    if (before !== '\n\n') {
                      if (before.endsWith('\n')) {
                        accumulatedText = accumulatedText.slice(0, startIdx) + '\n' + accumulatedText.slice(startIdx);
                        startIdx += 1; endIdx += 1;
                      } else {
                        accumulatedText = accumulatedText.slice(0, startIdx) + '\n\n' + accumulatedText.slice(startIdx);
                        startIdx += 2; endIdx += 2;
                      }
                    }
                    // 检查后面
                    const after = accumulatedText.slice(endIdx, endIdx + 2);
                    if (after !== '\n\n') {
                      if (after.startsWith('\n')) {
                        accumulatedText = accumulatedText.slice(0, endIdx) + '\n' + accumulatedText.slice(endIdx);
                      } else {
                        accumulatedText = accumulatedText.slice(0, endIdx) + '\n\n' + accumulatedText.slice(endIdx);
                      }
                    }
                  }
                  onChunk(chunkText, accumulatedText, 'llm');
                }
              }
            } catch (e) {
              console.warn('解析流式数据失败:', e, dataStr);
              // 如果不是JSON格式，检查是否是有效的文本内容
              if (dataStr && dataStr !== '[DONE]' && !dataStr.startsWith('{') && !dataStr.startsWith('[')) {
                // 只有当数据不是JSON格式时才作为文本处理
                accumulatedText += dataStr;
                onChunk(dataStr, accumulatedText);
              }
            }
          }
        }
      }

      const processingTime = Date.now() - startTime;

      // 清理累积文本，移除可能的JSON格式数据
      let cleanedText = accumulatedText || '抱歉，我暂时无法理解您的问题，请换个方式问我。';

      // 检查并清理JSON格式数据
      if (typeof cleanedText === 'string' &&
        (cleanedText.includes('{"result":') || cleanedText.includes('{"chat_history":'))) {
        // 如果检测到JSON格式数据，尝试清理
        try {
          const jsonMatch = cleanedText.match(/^(.*?)(\{.*\})$/s);
          if (jsonMatch) {
            cleanedText = jsonMatch[1].trim() || '抱歉，我暂时无法理解您的问题，请换个方式问我。';
          }
        } catch {
          cleanedText = '抱歉，我暂时无法理解您的问题，请换个方式问我。';
        }
      }

      // 计算时间延迟（转换为秒）
      const firstTokenDelta = firstTokenTime ? (firstTokenTime - startTime) / 1000 : undefined;
      const totalDelta = endTime ? (endTime - startTime) / 1000 : undefined;

      // 创建完整的消息对象
      const fullMessage: StreamMessage = {
        id: messageId,
        text: cleanedText,
        role: 'agent',
        status: 'sent',
        timestamp: Date.now(),
        contentType: 'markdown',
        metadata: {
          processingTime,
          serviceId: this.currentService,
          isStreamed: true,
          firstTokenTime: firstTokenDelta, // 首Token延迟(秒)
          totalDelta: totalDelta, // 总处理时间(秒)
        },
      };

      onComplete(fullMessage);

    } catch (error) {
      // 检查是否是因为手动终止导致的错误
      if (error instanceof Error && error.name === 'AbortError') {
        return; // 不调用onError，因为这是预期的行为
      }

      console.error('流式API调用失败:', error);
      onError(error instanceof Error ? error.message : '流式连接失败，请检查网络连接');
    } finally {
      this.currentController = null;
    }
  }

  // 终止当前的流式请求
  stopStream(): void {
    if (this.currentController) {
      this.currentController.abort();
      this.currentController = null;
    }
  }

  // 获取sessionId
  getSessionId(): string {
    return this.sessionId;
  }


}

export const streamApiService = new StreamApiService();